#define  _CRT_SECURE_NO_WARNINGS 1
//#include"head.h"

/*
 * 结构体实现位段
 *
 */

// 位段的声明和结构是类似的，有两个不同:
// 1. 位段的成员必须是 int、unsigned int 或signed int，在C99中位段成员的类型也可以选择其他类型。
// 2. 位段的成员名后边有一个冒号和一个数字。
//

////结构体：
//struct A
//{
//	int a;
//	int b;
//	int c;
//	int d;
//};
//
////位段：
//struct B
//{
//	int a:2; // --> 比特位
//	int b:5;
//	int c:10;
//    int d:30;
//};
//
//int main()
//{
//    printf("sizeof(struct A): %zd\n", sizeof(struct A)); // 16
//	printf("sizeof(struct B): %zd\n", sizeof(struct B)); // 8
//
//	//位段可以节省空间
//	/*
//	位段的内存分配
//	1. 位段的成员可以是 int unsigned int signed int 或者是 char 等类型
//	2. 位段的空间上是按照需要以4个字节(int)或者1个字节(char )的方式来开辟的。(如果不够的话，会按照4字节或者1字节再给分配)
//	3. 位段涉及很多不确定因素，位段是不跨平台的，注重可移植的程序应该避免使用位段。
//	*/
//
//	return 0; 
//}


//struct S
//{
//	char a : 3; // 大小不能超过该类型的大小
//    char b : 4;
//    char c : 5;
//    char d : 4;
//    //申请到的一个字节空间在使用时，从左向右使用还是从右(低)向左(高)使用是不确定的
//    //一个字节内剩余的空间不够下一个成员使用时，是否浪费，不确定
//    //
//};
//
//int main()
//{
//    struct S s = { 0 }; // 初始化-->所有的比特位都是0
//    //printf("sizeof(struct S): %zd\n", sizeof(struct S));
//
//    s.a = 10;
//    s.b = 12;
//    s.c = 3;
//    s.d = 4;
//
//    /*
//    位段的跨平台问题
//    1. int 位段被当成有符号数还是无符号数是不确定的。
//    2. 位段中最大位的数目不能确定。(16位机器最大16，32位机器最大32，写成27，在16位机器会出问题。)
//    3. 位段中的成员在内存中从左向右分配，还是从右向左分配，标准尚未定义。
//    4. 当一个结构包含两个位段，第二个位段成员比较大，无法容纳于第一个位段剩余的位时，是舍弃剩余的位还是利用，这是不确定的。
//    */
//
//    /*
//    位段使用的注意事项
//    位段的几个成员共有同一个字节，这样有些成员的起始位置并不是某个字节的起始位置，那么这些位置处是没有地址的。
//    内存中每个字节分配一个地址，一个字节内部的bit位是没有地址的。
//    
//    所以不能对位段的成员使用&操作符，这样就不能使用scanf直接给位段的成员输入值，只能是先输入放在一个变量中，然后赋值给位段的成员。
//    */
//
//
//    //scanf("%d", &s.a);//这是错误的
//
//    int b = 0;
//    scanf("%d", &b); // 正确
//    s.a = b;
//
//    return 0;
//}

